package com.naiterui.ehp.bp.domain;

import static javax.persistence.GenerationType.IDENTITY;

import java.io.Serializable;
import java.util.Date;
import java.util.HashMap;
import java.util.List;
import java.util.Map;

import javax.persistence.Basic;
import javax.persistence.Column;
import javax.persistence.Entity;
import javax.persistence.FetchType;
import javax.persistence.GeneratedValue;
import javax.persistence.Id;
import javax.persistence.JoinColumn;
import javax.persistence.Lob;
import javax.persistence.OneToMany;
import javax.persistence.Table;

/**
 * 医生基础信息
 *
 * @since 1.0.0
 */
@Entity
@Table(name = "doctor")
public class Doctor implements Serializable {

    // 医生标签--普通医生
    @Deprecated
    public static final int DOCTOR_LABLE_NOMAL = 0;
    // 医生标签--种子医生
    @Deprecated
    public static final int DOCTOR_LABLE_SEED = 1 << 0;
    // 医生标签--乡村医生
    @Deprecated
    public static final int DOCTOR_LABEL_COUNTRY = 1 << 1;
    // 医生标签--阳光化医生
    @Deprecated
    public static final int DOCTOR_LABEL_PUBLIC = 1 << 2;
    // 医生标签--正大天晴医生
    @Deprecated
    public static final int DOCTOR_LABEL_CTTQ = 1 << 3;
    // 医生标签--辉瑞医生
    @Deprecated
    public static final int DOCTOR_LABEL_PFIZER = 1 << 5;
    // 医生标签--用药提醒灰度范围
    @Deprecated
    public static final int DOCTOR_LABEL_MEDICINE_REMIND = 1 << 6;
    // 医生标签--诊所医生
    @Deprecated
    public static final int DOCTOR_LABEL_CLINIC = 1 << 15;
    // 医生标签--灰度下级患者输入身份证号医生
    @Deprecated
    public static final int DOCTOR_LABEL_FORCE_PT_IDNO = 1 << 16;
    // 医生标识--医嘱处方医生
    @Deprecated
    public static final int DOCTOR_LABEL_RECORD_RECOM = 1 << 17;
    // 医生标识--辉瑞男科--为张志超及相关男科医生建立
    @Deprecated
    public static final int DOCTOR_LABEL_PFIZER_NEW = 1 << 18;

    @Deprecated
    public static final Map<Integer, DoctorLable> LABEL_NAMES = new HashMap<>();

    //////////////////////////// 医生认证状态 ////////////////////////////
    /**
     * 认证状态: 0.未完善 1.待审核 2.已通过 3.不通过
     */
    /**
     * 未完善-医生帐号认证状态
     */
    public static final int AUTH_STATUS_NOT_PERFECTION = 0;
    /**
     * 待审核-医生帐号认证状态 原状态-审核中
     */
    public static final int AUTH_STATUS_AUDITING = 1;

    /**
     * 已通过-医生帐号认证状态 原状态-审核通过
     */
    public static final int AUTH_STATUS_SUCCESS = 2;

    /**
     * 不通过-医生帐号认证状态 原状态-审核不通过
     */
    public static final int AUTH_STATUS_REJECTED = 3;

    /**
     * 不通过-医生帐号认证状态 原状态-再次审核中
     */
    public static final int AUTH_STATUS_AGAIN = 3;

    /**
     * 资料未提交-医生帐号认证状态
     */
    public static final int AUTH_STATUS_UNCOMMITTED = 4;

    /**
     * 资料不完善-医生帐号认证状态
     */
    public static final int AUTH_STATUS_INCOMPLETE = 5;

    //////////////////////////// 医生备案状态 ////////////////////////////

    /**
     * 未备案-医生备案状态 原状态-未申请备案
     */
    public static final int RECORD_STATUS_NOT_APPLY = 0;

    /**
     * 备案中-医生备案状态 原状态-备案审核中
     */
    public static final int RECORD_STATUS_EXAMINEING = 1;

    /**
     * 已备案-医生备案状态 原状态-备案成功
     */
    public static final int RECORD_STATUS_SUCCESS = 2;

    /**
     * 不通过-医生备案状态 原状态-备案失败
     */
    public static final int RECORD_STATUS_FAIL = 3;

    /**
     * 医生备案状态 要求备案
     */
    public static final int RECORD_STATUS_REQUIREMENT = 4;

    /**
     * 医生备案状态 不需要备案
     */
    public static final int RECORD_STATUS_NO = 5;

    /**
     * 正式用户-医生用户类型
     */
    public static final int TYPE_FORMAL = 0;

    /**
     * 测试用户-医生用户类型
     */
    public static final int TYPE_TEST = 1;

    /**
     * 阳光化标识-否
     */
    public static final int PUBLIC_STATUS_NO = 1;

    /**
     * 阳光化标识-是
     */
    public static final int PUBLIC_STATUS_YES = 2;
    /**
     * 诊所医生标识-是
     */
    public static final int CLINIC_STATUS_YES = 1;
    /**
     * 诊所医生标识-否
     */
    public static final int CLINIC_STATUS_NO = 0;

    /**
     * 序列化id：<code>serialVersionUID</code>
     */
    private static final long serialVersionUID = -4343267038638753469L;

    static {
        LABEL_NAMES.put(DOCTOR_LABLE_SEED, new DoctorLable(3, "种子医生"));
        LABEL_NAMES.put(DOCTOR_LABEL_COUNTRY, new DoctorLable(2, "乡村医生"));
        // LABEL_NAMES.put(DOCTOR_LABLE_NOMAL, new DoctorLable(6, "普通医生"));
    }

    /**
     * 主键：<code>id</code>
     */
    private Long id;
    /**
     * 兼容旧版本userId：<code>userId</code>
     */
    private Long userId;
    /**
     * 姓名：<code>name</code>
     */
    private String name;
    /**
     * 性别：<code>gender</code>
     */
    private Integer gender;
    /**
     * 联系电话：<code>phone</code>
     */
    private String phone;
    /**
     * 认证状态0.未认证 1.认证中 2.已认证 3.不通过
     */
    private Integer status;
    /**
     * 字段或域定义：<code>titleId</code>
     */
    private Integer titleId;
    /**
     * 科室id：<code>departmentId</code>
     */
    private Integer departmentId;
    /**
     * 自定义科室名：<code>customDepartment</code>
     */
    private String customDepartment;
    /**
     * 医院id：<code>hospitalId</code>
     */
    private Integer hospitalId;
    /**
     * 自定义医院名：<code>hospitalName</code>
     */
    private String hospitalName;
    /**
     * 医生简介：<code>introduction</code>
     */
    private String introduction;
    /**
     * 专业与专长：<code>expertise</code>
     */
    private String expertise;
    /**
     * 医院出诊时间：<code>consultationHospital</code>
     */
    private String consultationHospital;
    /**
     * 门诊地址：<code>outpatienOn</code>
     */
    private String outpatienOn;
    /**
     * 账户状态0:正常，1:禁用：<code>accountStatus</code>
     */
    private Integer accountStatus;
    /**
     * 头像地址：<code>headUrl</code>
     */
    private String headUrl;
    /**
     * 城市id：<code>cityId</code>
     */
    private Integer cityId;
    /**
     * 推荐码：<code>recommCode</code>
     */
    private String recommCode;
    /**
     * 创建时间：<code>createdAt</code>
     */
    private Date createdAt;
    /**
     * 修改时间：<code>changedAt</code>
     */
    private Date changedAt;

    private String changedBy;
    /**
     * 测试帐号状态：0正式，1测试：<code>type</code>
     */
    private Integer type;
    /**
     * 用户标签类型:0：默认无标签；1.种子医生标签 <code>labelType</code>
     */
    private Integer labelType;
    /**
     * 合作方ID：<code>partnerId</code>
     */
    private Long partnerId;

    /**
     * 身份证号 请使用dr_licence 中的number
     */
    @Deprecated
    private String idNo;

    /**
     * 资格证号 请使用dr_licence 中的number
     */
    @Deprecated
    private String certNo;

    /**
     * 多点执业状态: 0.未备案 1.备案中 2.已备案 3.不通过
     */
    private Integer recordStatus;

    /**
     * 医生提交审核时间：<code>submitAuditTime</code>
     */
    private Date submitAuditTime;

    /**
     * 签名图片路径
     */
    private String sealImageOrigin;
    /**
     * 签名图片路径
     */
    private String sealImage;
    /**
     * 电子邮箱
     */
    private String email;
    private List<UserLabel> userLabel;
    /**
     * 医生阳光化标示，1：非阳光化，2：阳光化：<code>publicStatus</code>
     * 默认非阳光化医生，
     * 该字段已弃用，阳光化标记根据labelType进行判断
     */
    @Deprecated
    private Integer isPublic = Doctor.PUBLIC_STATUS_NO;

    public Doctor() {
    }

    public Doctor(Long id, Integer status) {
        this.id = id;
        this.status = status;
    }

    @Id
    @GeneratedValue(strategy = IDENTITY)
    @Column(name = "id", unique = true, nullable = false)
    public Long getId() {
        return this.id;
    }

    public void setId(Long id) {
        this.id = id;
    }

    @Column(name = "user_id")
    public Long getUserId() {
        return this.userId;
    }

    public void setUserId(Long userId) {
        this.userId = userId;
    }

    @Column(name = "name", length = 45)
    public String getName() {
        return this.name;
    }

    public void setName(String name) {
        this.name = name;
    }

    @Column(name = "gender")
    public Integer getGender() {
        return this.gender;
    }

    public void setGender(Integer gender) {
        this.gender = gender;
    }

    @Column(name = "phone", length = 11)
    public String getPhone() {
        return this.phone;
    }

    public void setPhone(String phone) {
        this.phone = phone;
    }

    @Column(name = "status")
    public Integer getStatus() {
        return this.status;
    }

    public void setStatus(Integer status) {
        this.status = status;
    }

    @Column(name = "title_id")
    public Integer getTitleId() {
        return this.titleId;
    }

    public void setTitleId(Integer titleId) {
        this.titleId = titleId;
    }

    @Column(name = "department_id")
    public Integer getDepartmentId() {
        return this.departmentId;
    }

    public void setDepartmentId(Integer departmentId) {
        this.departmentId = departmentId;
    }

    @Column(name = "custom_department")
    public String getCustomDepartment() {
        return this.customDepartment;
    }

    public void setCustomDepartment(String customDepartment) {
        this.customDepartment = customDepartment;
    }

    @Column(name = "hospital_id")
    public Integer getHospitalId() {
        return this.hospitalId;
    }

    public void setHospitalId(Integer hospitalId) {
        this.hospitalId = hospitalId;
    }

    @Column(name = "hospital_name")
    public String getHospitalName() {
        return this.hospitalName;
    }

    public void sethospitalName(String hospitalName) {
        this.hospitalName = hospitalName;
    }

    @Lob
    @Basic(fetch = FetchType.LAZY)
    @Column(name = "introduction", columnDefinition = "TEXT", length = 65535)
    public String getIntroduction() {
        return this.introduction;
    }

    public void setIntroduction(String introduction) {
        this.introduction = introduction;
    }

    @Lob
    @Basic(fetch = FetchType.LAZY)
    @Column(name = "expertise", columnDefinition = "TEXT", length = 65535)
    public String getExpertise() {
        return this.expertise;
    }

    public void setExpertise(String expertise) {
        this.expertise = expertise;
    }

    @Column(name = "outpatien_on", length = 45)
    public String getOutpatienOn() {
        return this.outpatienOn;
    }

    public void setOutpatienOn(String outpatienOn) {
        this.outpatienOn = outpatienOn;
    }

    @Column(name = "account_status")
    public Integer getAccountStatus() {
        return this.accountStatus;
    }

    public void setAccountStatus(Integer accountStatus) {
        this.accountStatus = accountStatus;
    }

    @Column(name = "head_url")
    public String getHeadUrl() {
        return this.headUrl;
    }

    public void setHeadUrl(String headUrl) {
        this.headUrl = headUrl;
    }

    @Column(name = "city_id")
    public Integer getCityId() {
        return this.cityId;
    }

    public void setCityId(Integer cityId) {
        this.cityId = cityId;
    }

    @Column(name = "recomm_code", nullable = false, length = 256)
    public String getRecommCode() {
        return this.recommCode;
    }

    public void setRecommCode(String recommCode) {
        this.recommCode = recommCode;
    }

    @Column(name = "created_at")
    public Date getCreatedAt() {
        return this.createdAt;
    }

    public void setCreatedAt(Date createdAt) {
        this.createdAt = createdAt;
    }

    @Column(name = "changed_at")
    public Date getChangedAt() {
        return this.changedAt;
    }

    public void setChangedAt(Date changedAt) {
        this.changedAt = changedAt;
    }

    @Column(name = "type")
    public Integer getType() {
        return this.type;
    }

    public void setType(Integer type) {
        this.type = type;
    }

    @Column(name = "label_type")
    public Integer getLabelType() {
        return this.labelType;
    }

    public void setLabelType(Integer labelType) {
        this.labelType = labelType;
    }

    /**
     * @return Long 取得域 partnerId 的方法。
     */
    @Column(name = "partner_id")
    public Long getPartnerId() {
        return this.partnerId;
    }

    /**
     * @param partnerId 对域 partnerId 的设置方法.
     */
    public void setPartnerId(Long partnerId) {
        this.partnerId = partnerId;
    }

    @Column(name = "submit_audit_time")
    public Date getSubmitAuditTime() {
        return this.submitAuditTime;
    }

    public void setSubmitAuditTime(Date submitAuditTime) {
        this.submitAuditTime = submitAuditTime;
    }

    @Deprecated
    @Column(name = "id_no")
    public String getIdNo() {
        return this.idNo;
    }

    @Deprecated
    public void setIdNo(String idNo) {
        this.idNo = idNo;
    }

    @Deprecated
    @Column(name = "cert_no")
    public String getCertNo() {
        return this.certNo;
    }

    @Deprecated
    public void setCertNo(String certNo) {
        this.certNo = certNo;
    }

    @Column(name = "record_status")
    public Integer getRecordStatus() {
        return this.recordStatus;
    }

    public void setRecordStatus(Integer recordStatus) {
        this.recordStatus = recordStatus;
    }

    @Column(name = "seal_image_origin")
    public String getSealImageOrigin() {
        return sealImageOrigin;
    }

    public void setSealImageOrigin(String sealImageOrigin) {
        this.sealImageOrigin = sealImageOrigin;
    }

    @Column(name = "seal_image")
    public String getSealImage() {
        return sealImage;
    }

    public void setSealImage(String sealImage) {
        this.sealImage = sealImage;
    }

    @Deprecated
    @Column(name = "is_public")
    public Integer getIsPublic() {
        return this.isPublic;
    }

    @Deprecated
    public void setIsPublic(Integer isPublic) {
        this.isPublic = isPublic;
    }

    @Column(name = "changed_by")
    public String getChangedBy() {
        return changedBy;
    }

    public void setChangedBy(String changedBy) {
        this.changedBy = changedBy;
    }

    @Column(name = "email")
    public String getEmail() {
        return email;
    }

    public void setEmail(String email) {
        this.email = email;
    }

    @OneToMany
    @JoinColumn(name = "user_id", referencedColumnName = "id", insertable = false, updatable = false)
    public List<UserLabel> getUserLabel() {
        return userLabel;
    }

    public void setUserLabel(List<UserLabel> userLabel) {
        this.userLabel = userLabel;
    }

    /**
     * 验证医生是否包含指定标签：V3.2.0停用，获取医生标签找 周培培/范文东
     * Doctor.validateLabel()
     *
     * @param label DOCTOR_LABLE_NOMAL,DOCTOR_LABLE_SEED,DOCTOR_LABEL_COUNTRY
     *
     * @return
     *
     * @Author Amber
     * @Date 2016年8月15日
     * @since 1.0.0
     */
    @Deprecated
    public boolean validateLabel(Integer label) {
        if ((this.labelType & label) == label) {
            return true;
        }
        return false;
    }


    public static class DoctorLable implements Comparable {

        /**
         * 排序1 2 3 4 最小的放到最上面
         */
        private Integer odrer;

        /**
         * 标签名称
         */
        private String name;

        public DoctorLable(Integer odrer, String name) {
            this.odrer = odrer;
            this.name = name;
        }

        public Integer getOdrer() {
            return this.odrer;
        }

        public void setOdrer(Integer odrer) {
            this.odrer = odrer;
        }

        public String getName() {
            return this.name;
        }

        public void setName(String name) {
            this.name = name;
        }

        @Override
        public int compareTo(Object o) {
            DoctorLable doctorLable = (DoctorLable) o;
            return Long.compare(this.odrer, doctorLable.getOdrer());
        }

        @Override
        public String toString() {
            return "DoctorLable{" + "odrer=" + this.odrer + ", name='" + this.name + '\'' + '}';
        }
    }
}